package qhLoading.loaders 
{
	import flash.display.Loader;
	import flash.display.LoaderInfo;
	import flash.events.*;
	import flash.net.*;
	import flash.utils.*;
	
	import qhLoading.LoaderErrorEvent;
	import qhLoading.info.ResourceInfo;
	
	/**
	 * 基础的加载器
	 * @author gcxk721
	 */
	public class QhLoader extends EventDispatcher 
	{
		
		private var _url : String;
        private var _urlLoader : URLLoader;
        private var _contentType : String;
        private var _loaderInfo : LoaderInfo;
        protected var _resourceInfo : ResourceInfo;
		
		public function QhLoader() 
		{
			
		}
		
		public function get resourceInfo() : ResourceInfo
        {
            return _resourceInfo;
        }

        public function load(url : String, info : ResourceInfo) : void
        {
            _resourceInfo = info;
            _url = url;
            initLoader();
        }

        private function initLoader() : void
        {
            _urlLoader = new URLLoader();
            _urlLoader.dataFormat = URLLoaderDataFormat.BINARY;
            _urlLoader.addEventListener(Event.COMPLETE, onCompleteHandler);
            _urlLoader.addEventListener(ProgressEvent.PROGRESS, onProgressHandler);
            _urlLoader.addEventListener(IOErrorEvent.IO_ERROR, onIOError);
            _urlLoader.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onIOError);
            _urlLoader.load(new URLRequest(_url));
        }

        protected function onCompleteHandler(event:Event) : void
        {
			var urloader : URLLoader = event.target as URLLoader;
			urloader.removeEventListener(Event.COMPLETE, onCompleteHandler);
			urloader.removeEventListener(ProgressEvent.PROGRESS, onProgressHandler);
			urloader.removeEventListener(IOErrorEvent.IO_ERROR, onIOError);
			urloader.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, onIOError);
            try
            {
				urloader.close();
            }
            catch (e:Error)
            {
            }
            streamloadComplete(event.target.data);
            initialize(event.target.data);
			urloader = null;
        }

        protected function streamloadComplete(bytes : ByteArray) : void
        {
            
        }

        protected function onProgressHandler(event:ProgressEvent) : void
        {
            dispatchEvent(event);
            
        }

        private function onIOError(event:ErrorEvent) : void
        {
			var urloader : URLLoader = event.target as URLLoader;
			urloader.removeEventListener(Event.COMPLETE, onCompleteHandler);
			urloader.removeEventListener(ProgressEvent.PROGRESS, onProgressHandler);
			urloader.removeEventListener(IOErrorEvent.IO_ERROR, onIOError);
			urloader.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, onIOError);
            onIOErrorHandler(event);
            
        }

        protected function onIOErrorHandler(event:ErrorEvent) : void
        {
            dispatchEvent(new LoaderErrorEvent(event.text));
        }

        public function initialize(bytes : *) : void
        {
            if (!(bytes is ByteArray))
            {
                throw new Error("Default Resource can only process ByteArrays!");
            }
            var loader : Loader = new Loader();
            loader.contentLoaderInfo.addEventListener(Event.COMPLETE, onLoadComplete);
            loader.contentLoaderInfo.addEventListener(IOErrorEvent.IO_ERROR, onChangeIOErrorHandler);
            loader.contentLoaderInfo.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onChangeIOErrorHandler);
            loader.loadBytes(bytes);
        }

        protected function onContentReady(value : Object) : Boolean
        {
            return true;
        }

        private function onLoadComplete(event : Event) : void
        {
            var loaderInfo : LoaderInfo = event.target as LoaderInfo;
            _loaderInfo = loaderInfo;
            loaderInfo.removeEventListener(Event.COMPLETE, onLoadComplete);
            loaderInfo.removeEventListener(IOErrorEvent.IO_ERROR, onChangeIOErrorHandler);
            loaderInfo.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, onChangeIOErrorHandler);
            if (onContentReady(event ? (event.target.content) : (null)))
            {
                onLoadCompleteHandler();
            }  
        }

        protected function onLoadCompleteHandler() : void
        {
            dispatchEvent(new Event(Event.COMPLETE));
        }

        private function onChangeIOErrorHandler(event:IOErrorEvent) : void
        {
             var loaderInfo : LoaderInfo = event.target as LoaderInfo;
            loaderInfo.removeEventListener(Event.COMPLETE, onLoadComplete);
            loaderInfo.removeEventListener(IOErrorEvent.IO_ERROR, onChangeIOErrorHandler);
            loaderInfo.removeEventListener(SecurityErrorEvent.SECURITY_ERROR, onChangeIOErrorHandler);
            onIOErrorHandler(event);
        }

        public function dispose() : void
        {
            _resourceInfo = null;
            _url = null;
            _loaderInfo = null;
        }

        public function get url() : String
        {
            return _url;
        }

        public function get contentType() : String
        {
            if (_loaderInfo)
            {
                return _loaderInfo.contentType;
            }
            return null;
        }

        public function get loaderInfo() : LoaderInfo
        {
            return _loaderInfo;
        }
		
	}

}